package com.laoli.lab37;

import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutionException;

/**
 * CompletableFuture示例4-回调处理
 */
public class CompletableFutureDemo04 {
    /**
     * 主线程的任务
     */
    private static void mainTask() {
        // 每隔1秒一次，连续5次输出信息
        for (int i = 1; i <= 5; i++) {
            try {
                System.out.printf("【主线程】执行任务%d：%s\n", i,
                        LocalTime.now().format(DateTimeFormatter.ofPattern("HH:mm:ss")));
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }
        }
    }

    /**
     * main方法
     */
    public static void main(String[] args) throws ExecutionException, InterruptedException {
        // 主线程执行任务-1
        mainTask();
        // 子线程执行有返回值的异步操作
        CompletableFuture.supplyAsync(() -> {
                    System.out.printf("\t【子线程】开始耗时任务：%s\n",
                            LocalTime.now().format(DateTimeFormatter.ofPattern("HH:mm:ss")));
                    System.out.printf("\t【子线程】当前线程：%s\n",Thread.currentThread().getName());
                    try {
                        Thread.sleep(3000); // 模拟耗时操作（如数据库查询、网络请求）
                    } catch (InterruptedException e) {
                        throw new RuntimeException(e);
                    }
                    return "SubTask is Done";//有返回值
                })
                //再次加工，也就是再做一些逻辑处理
                .thenApplyAsync(result -> {
                    System.out.printf("\t【Apply】当前线程：%s\n",Thread.currentThread().getName());
                    return result.toUpperCase();//有返回值
                })
                // 当主线程需要结果时
                .thenAcceptAsync(result -> {//这种方式获取结果，将不会阻塞主线程
                    // 最终消费逻辑
                    System.out.printf("\t【子线程】返回子线程的执行结果(%s)：%s\n",
                            result,
                            LocalTime.now().format(DateTimeFormatter.ofPattern("HH:mm:ss")));
                    System.out.printf("\t【Accept】当前线程：%s\n",Thread.currentThread().getName());
                });
        // 主线程执行任务-2
        mainTask();
    }
}
